package com.xiaolin.sports.utils;

import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.nio.file.Paths;
import java.util.UUID;

import org.apache.commons.io.FileUtils;

import com.alibaba.fastjson.JSONObject;
import com.google.gson.Gson;
import com.qiniu.common.QiniuException;
import com.qiniu.common.Zone;
import com.qiniu.http.Response;
import com.qiniu.storage.Configuration;
import com.qiniu.storage.UploadManager;
import com.qiniu.storage.persistent.FileRecorder;
import com.qiniu.util.Auth;
import com.qiniu.util.StringMap;
import com.xiaolin.sports.common.QiniuConst;
import com.xiaolin.sports.common.enums.MimeType;
import com.xiaolin.sports.model.MyPutRet;

public class QiniuUtil {
	
	public static MyPutRet fileBreankPointUpload(String localFilePath, String bucket) {
		//构造一个带指定Zone对象的配置类
		Configuration cfg = new Configuration(Zone.zone2());
		//...其他参数参考类注释
		String accessKey = QiniuConst.ACCESSKEY;
		String secretKey = QiniuConst.SECRETKEY;
		//默认不指定key的情况下，以文件内容的hash值作为文件名
		String key = null;
		Auth auth = Auth.create(accessKey, secretKey);
		StringMap putPolicy = new StringMap();
		putPolicy.put("callbackUrl", "http://api.example.com/qiniu/upload/callback");
		putPolicy.put("callbackBody", "{\"key\":\"$(key)\",\"hash\":\"$(etag)\",\"bucket\":\"$(bucket)\",\"fsize\":$(fsize),\"mimeType\":$(mimeType)}");
		putPolicy.put("callbackBodyType", "application/json");
		long expireSeconds = 3600;
		String upToken = auth.uploadToken(bucket, null, expireSeconds, putPolicy);
		String localTempDir = Paths.get(System.getenv("java.io.tmpdir"), bucket).toString();
		try {
		    //设置断点续传文件进度保存目录
		    FileRecorder fileRecorder = new FileRecorder(localTempDir);
		    UploadManager uploadManager = new UploadManager(cfg, fileRecorder);
	        Response response = uploadManager.put(localFilePath, key, upToken);
	        //解析上传成功的结果
	        MyPutRet putRet = new Gson().fromJson(response.bodyString(), MyPutRet.class);
	        return putRet;
		} catch (Exception ex) {
		    ex.printStackTrace();
		}
		return null;
	}
	
	public static MyPutRet thirdFileUpload(String thirdFilePath, String bucket) {
		return thirdFileUpload(thirdFilePath, bucket, null);
	}
	
	public static MyPutRet thirdFileUpload(String thirdFilePath, String bucket, String fileUrl) {
		//构造一个带指定Zone对象的配置类
				Configuration cfg = new Configuration(Zone.zone2());
				//...其他参数参考类注释
				UploadManager uploadManager = new UploadManager(cfg);
				//...生成上传凭证，然后准备上传
				String accessKey = QiniuConst.ACCESSKEY;
				String secretKey = QiniuConst.SECRETKEY;
				//默认不指定key的情况下，以文件内容的hash值作为文件名
				String key = fileUrl;
				try {
					URL url = new URL(thirdFilePath);
		    		HttpURLConnection conn = (HttpURLConnection) url.openConnection();
		    		conn.setRequestMethod("GET");
		    		conn.setDoInput(true);
		    		if ( HttpURLConnection.HTTP_OK != conn.getResponseCode()) {
						return null;
					}
		    		
		    		String suffix = MimeType.getKey(conn.getContentType());
		    		
		    		String fileName = UUID.randomUUID().toString() + "." + suffix;
		    		
		    		File tmpFile = saveFileByInputStream(conn.getInputStream(), fileName);
		    		
		    		Auth auth = Auth.create(accessKey, secretKey);
				    StringMap putPolicy = new StringMap();
					putPolicy.put("returnBody", "{\"key\":\"$(key)\",\"hash\":\"$(etag)\",\"bucket\":\"$(bucket)\",\"fsize\":$(fsize)}");
					long expireSeconds = 3600;
					
					String upToken = auth.uploadToken(bucket, null, expireSeconds, putPolicy);
					Response response = uploadManager.put(tmpFile.getPath(), key, upToken);
			        //解析上传成功的结果
			        MyPutRet putRet = new Gson().fromJson(response.bodyString(), MyPutRet.class);
			       
			        tmpFile.delete();
			        conn.disconnect();
			        return putRet;
				} catch (Exception ex) {
				    ex.printStackTrace();
				}
				return null;
	}
	
	public static MyPutRet fileUpload(String localFilePath, String bucket, boolean isDelete){
		//构造一个带指定Zone对象的配置类
		Configuration cfg = new Configuration(Zone.zone2());
		//...其他参数参考类注释
		UploadManager uploadManager = new UploadManager(cfg);
		//...生成上传凭证，然后准备上传
		String accessKey = QiniuConst.ACCESSKEY;
		String secretKey = QiniuConst.SECRETKEY;
		//默认不指定key的情况下，以文件内容的hash值作为文件名
		String key = null;
		Auth auth = Auth.create(accessKey, secretKey);
		StringMap putPolicy = new StringMap();
		putPolicy.put("returnBody", "{\"key\":\"$(key)\",\"hash\":\"$(etag)\",\"bucket\":\"$(bucket)\",\"fsize\":$(fsize)}");
		long expireSeconds = 3600;
		String upToken = auth.uploadToken(bucket, null, expireSeconds, putPolicy);
		try {
		    Response response = uploadManager.put(localFilePath, key, upToken);
		    //解析上传成功的结果
		    MyPutRet putRet = new Gson().fromJson(response.bodyString(), MyPutRet.class);
		    if(isDelete) new File(localFilePath).delete();
		    return putRet;
		} catch (QiniuException ex) {
		    ex.printStackTrace();
		}
		return null;
	}
	
	public static File saveFileByInputStream(InputStream is, String fileName) {

		File tmpFile = getTmpFile(fileName);

		byte[] dataBuf = new byte[ 2048 ];
		BufferedInputStream bis = new BufferedInputStream(is, 8192);
		try {
			BufferedOutputStream bos = new BufferedOutputStream(
					new FileOutputStream(tmpFile), 8192);

			int count = 0;
			while ((count = bis.read(dataBuf)) != -1) {
				bos.write(dataBuf, 0, count);
			}
			bos.flush();
			bos.close();
		} catch (IOException e) {
			e.printStackTrace();
		}
		return tmpFile;
	}

	private static File getTmpFile(String fileName) {
		File tmpDir = FileUtils.getTempDirectory();
		return new File(tmpDir, fileName);
	}
	
	public static void main(String[] args) {
		try {
//			MyPutRet myPutRet = QiniuUtil.thirdFileUpload("https://mmbiz.qlogo.cn/mmbiz_png/JkjsN8RS6oDl30V798PunAaJDo5tXda5PoomK7gcxX79JR21UQna6nN26hZ5xTm74mZVWUu0rk1v20SSMBoAEg/0?wx_fmt=png", QiniuConst.BUCKET);
//			System.out.println(JSONObject.toJSONString(myPutRet));
			System.out.println(UUID.randomUUID().toString().replaceAll("-", ""));
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

}
